/*
    bytefyte
    Copyright (C) 2008, bytefyte

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.

*/
#ifndef ALLPROTOCOLS_H_
#define ALLPROTOCOLS_H_

/*
IMPORTANT_NOTICE_TO_HACKERS

all header structs are to be of a format:
typedef struct protocol_header
{
}protocol_header

in case header length can't be calculated from a field in the protocol,
define a #define of the format SIZE_PROTOCOL_HEADER to the number of the
bytes which is to be the header length.
eg: #define SIZE_ETH_HEADER 14
*/

#define ETHER_ADDR_LEN  6

/* Ethernet header */
typedef struct eth_header
{
	u_char dhost[ETHER_ADDR_LEN]; /* Destination host address */
	u_char shost[ETHER_ADDR_LEN]; /* Source host address */
	u_short ether_type; /* IP? ARP? RARP? etc */
}eth_header;
#define SIZE_ETH_HEADER 14

/* ARP header[ether_type=0x0806] */
typedef struct arp_header
{
    u_short htype;
    u_short ptype;
    u_char  hlen;
    u_char  plen;
    u_short op;
}arp_header;
#define SIZE_ARP_HEADER 8

/* RARP header[ether_type=0x8035] */
typedef struct rarp_header
{
    u_short htype;
    u_short ptype;
    u_char  hlen;
    u_char  plen;
    u_short op;
}rarp_header;
#define SIZE_RARP_HEADER 8

/* 4 bytes IP address */
typedef struct ip_address
{
	u_char byte1;
	u_char byte2;
	u_char byte3;
	u_char byte4;
}ip_address;

/* IPv4 header[ether_type:0x0800] */
typedef struct ip_header
{
	u_char	ver_ihl;		// Version (4 bits) + Internet header length (4 bits)
	u_char	tos;			// Type of service 
	u_short tlen;			// Total length 
	u_short identification; // Identification
	u_short flags_fo;		// Flags (3 bits) + Fragment offset (13 bits)
	u_char	ttl;			// Time to live
	u_char	proto;			// Protocol
	u_short crc;			// Header checksum
	ip_address	saddr;		// Source address
	ip_address	daddr;		// Destination address
	u_int	op_pad;			// Option + Padding
}ip_header;
	#define IP_HL(ip)               (((ip)->ver_ihl) & 0x0f)
	#define IP_V(ip)                (((ip)->ip_vhl) >> 4)

/* ICMP header [ip->proto=1] */
typedef struct icmp_header
{
	u_char type;
	u_char code;
	u_short cksum;
	u_short id;
	u_short seq;
}icmp_header;
#define SIZE_ICMP_HEADER 8

/* IGMP header [ip->proto=2] */
typedef struct igmp_header
{
	u_char type;
	u_char code;
	u_short cksum;
	u_long group;
}igmp_header;
#define SIZE_IGMP_HEADER 8

/* TCP header [ip->proto=6] */
// options and padding have been left out
typedef struct tcp_header
{
	u_short sport;       /* source port */
	u_short dport;       /* destination port */
	u_int seq;         /* sequence number */
	u_int ack;         /* acknowledgement number */
	u_char offx2;        /* data offset, rsvd */
		#define TH_OFF(th)      (((th)->offx2 & 0xf0) >> 4)
	u_char flags;
		#define TH_FIN 0x01
		#define TH_SYN 0x02
		#define TH_RST 0x04
        	#define TH_PUSH 0x08
        	#define TH_ACK 0x10
        	#define TH_URG 0x20
        	#define TH_ECE 0x40
        	#define TH_CWR 0x80
	u_short win;         /* window */
	u_short sum;         /* checksum */
	u_short urp;         /* urgent pointer */
}tcp_header;
#define SIZE_TCP_HEADER 20

/* SCTP header [ip->proto=132] */
typedef struct sctp_header
{
	u_short sport;       /* source port */
	u_short dport;       /* destination port */
	u_int vtag;         /* verification tag */
	u_int cksum;         /* checksum[uses the Adler-32 algorithm] */
	u_char chnktype;
	u_char chnkflags;
	u_short chnklength;
}sctp_header;
#define SIZE_SCTP_HEADER 16

/* UDP header [ip->proto=17] */
typedef struct udp_header
{
	u_short sport;			// Source port
	u_short dport;			// Destination port
	u_short len;			// Datagram length
	u_short crc;			// Checksum
}udp_header;
#define SIZE_UDP_HEADER 8

/* DHCP header [udp->dport=67/68] */
typedef struct dhcp_header
{
	u_char op;
	u_char htype;
	u_char halen;
	u_char hops;
	u_long tid;
	u_short secs_booted;
	u_short flags;
	ip_address ciaddr;
	ip_address yiaddr;
	ip_address siaddr;
	ip_address giaddr;
	u_char chaddr[16];
	char shname[64];
	char bfile[128];
}dhcp_header;
#define SIZE_DHCP_HEADER 256

/* DNS header [tcp->dport=53] */
typedef struct dns_header
{
	u_short id;
	u_char qr:1;
	u_char op:4;
	u_char aa:1;
	u_char tc:1;
	u_char rd:1;
	u_char ra:1;
	u_char z:1;
	u_char ad:1;
	u_char cd:1;
	u_char rcode:4;
	u_short totq;
	u_short totansrr;
	u_short totauthrr;
	u_short totaddrr;
}dns_header
#define SIZE_DNS_HEADER 12

	/* to be used alongwith dns_header */
	typedef struct dn_query
	{
		char *name;
		u_short type;
		u_short class;
	}dn_query;
	
	/* to be used alongwith dns_header */
	typedef struct dn_rr
	{
		char *name; //the last two bytes are the offset from the start of the dns header
		u_short type;
		u_short class;
		u_long ttl;
		u_short datalen;
		char *data;
	}dn_rr;

/* DCAP header [tcp->dport=1973] */
typedef struct dcap_header
{
	u_char proto_ver; //always 0x81
	u_char type;
	u_short totlen;
}dcap_header
#define SIZE_DCAP_HEADER 4

#endif //ALLPROTOCOLS_H_
